package com.demo.easyExcel.APIDemo.write;

import com.alibaba.excel.EasyExcel;
import com.alibaba.excel.ExcelWriter;
import com.alibaba.excel.util.FileUtils;
import com.alibaba.excel.write.metadata.WriteSheet;
import com.demo.easyExcel.APIDemo.read.ComplexHeadData;
import com.demo.easyExcel.APIDemo.read.DemoData;
import com.demo.easyExcel.APIDemo.read.ImageData;
import com.demo.easyExcel.APIDemo.read.IndexData;
import org.junit.Test;

import java.io.File;
import java.io.InputStream;
import java.net.URL;
import java.util.*;

public class test {
    String fileName = "C:\\Users\\Administrator\\Desktop\\excel\\excel2.xls";
    private List<DemoData> data() {
        List<DemoData> list = new ArrayList<DemoData>();
        for (int i = 0; i < 10; i++) {
            DemoData data = new DemoData();
            data.setString("字符串" + i);
            data.setDate(new Date());
            data.setDoubleData(0.56);
            list.add(data);
        }
        return list;
    }
    @Test
    public void simpleWrite() {

        // 这里 需要指定写用哪个class去写，然后写到第一个sheet，名字为模板 然后文件流会自动关闭
        // 如果这里想使用03 则 传入excelType参数即可
        EasyExcel.write(fileName, DemoData.class).sheet("模板").doWrite(data());


//        // 这里 需要指定写用哪个class去写
//        ExcelWriter excelWriter = EasyExcel.write(fileName, DemoData.class).build();
//        WriteSheet writeSheet = EasyExcel.writerSheet("模板").build();
//        excelWriter.write(data(), writeSheet);
//        // 千万别忘记finish 会帮忙关闭流
//        excelWriter.finish();
    }

    /**
     * 根据参数只导出指定列
     * <p>
     * 1. 创建excel对应的实体对象 参照{@link DemoData}
     * <p>
     * 2. 根据自己或者排除自己需要的列
     * <p>
     * 3. 直接写即可
     *
     *
     * 包括哪些字段或者
     * 排除哪些字段
     *
     * @since 2.1.1
     */
    @Test
    public void excludeOrIncludeWrite() {

        // 根据用户传入字段 假设我们要忽略 date
        Set<String> excludeColumnFiledNames = new HashSet<String>();
        excludeColumnFiledNames.add("string");
        // 这里 需要指定写用哪个class去写，然后写到第一个sheet，名字为模板 然后文件流会自动关闭
        EasyExcel.write(fileName, DemoData.class).excludeColumnFiledNames(excludeColumnFiledNames).sheet("模板")
                .doWrite(data());

        fileName = fileName + System.currentTimeMillis() + ".xlsx";
        // 根据用户传入字段 假设我们只要导出 date
        Set<String> includeColumnFiledNames = new HashSet<String>();
        includeColumnFiledNames.add("date");
        // 这里 需要指定写用哪个class去写，然后写到第一个sheet，名字为模板 然后文件流会自动关闭
        EasyExcel.write(fileName, DemoData.class).includeColumnFiledNames(includeColumnFiledNames).sheet("模板")
                .doWrite(data());
    }

    /**
     * 指定写入的列
     * <p>1. 创建excel对应的实体对象 参照{@link IndexData}
     * <p>3. 直接写即可
     */
    @Test
    public void indexWrite() {
        fileName=fileName+"index.xlsx";
        // 这里 需要指定写用哪个class去写，然后写到第一个sheet，名字为模板 然后文件流会自动关闭
        EasyExcel.write(fileName, IndexData.class).sheet("模板").doWrite(data());
    }
    /**
     * 复杂头写入
     * <p>1. 创建excel对应的实体对象 参照{@link ComplexHeadData}
     * <p>3. 直接写即可
     */
    @Test
    public void complexHeadWrite() {

        // 这里 需要指定写用哪个class去写，然后写到第一个sheet，名字为模板 然后文件流会自动关闭
        EasyExcel.write(fileName, ComplexHeadData.class).sheet("模板").doWrite(data());
    }

    /**
     * 重复多次写入(写到单个或者多个Sheet)
     * <p>
     * 1. 创建excel对应的实体对象 参照{@link ComplexHeadData}
     * <p>
     * <p>
     * 3. 直接调用二次写入即可
     */
    @Test
    public void repeatedWrite() {
        // 方法1 如果写到同一个sheet
        // 这里 需要指定写用哪个class去写
        ExcelWriter excelWriter = EasyExcel.write(fileName, DemoData.class).build();
        // 这里注意 如果同一个sheet只要创建一次
        WriteSheet writeSheet = EasyExcel.writerSheet("模板").build();
        // 去调用写入,这里我调用了五次，实际使用时根据数据库分页的总的页数来
        for (int i = 0; i < 5; i++) {
            // 分页去数据库查询数据 这里可以去数据库查询每一页的数据
            List<DemoData> data = data();
            excelWriter.write(data, writeSheet);
        }
        // 千万别忘记finish 会帮忙关闭流
        excelWriter.finish();

//        // 方法2 如果写到不同的sheet 同一个对象
//        // 这里 指定文件
//        excelWriter = EasyExcel.write(fileName, DemoData.class).build();
//        // 去调用写入,这里我调用了五次，实际使用时根据数据库分页的总的页数来。这里最终会写到5个sheet里面
//        for (int i = 0; i < 5; i++) {
//            // 每次都要创建writeSheet 这里注意必须指定sheetNo
//            writeSheet = EasyExcel.writerSheet(i, "模板").build();
//            // 分页去数据库查询数据 这里可以去数据库查询每一页的数据
//            List<DemoData> data = data();
//            excelWriter.write(data, writeSheet);
//        }
//        // 千万别忘记finish 会帮忙关闭流
//        excelWriter.finish();
//
//        // 方法3 如果写到不同的sheet 不同的对象
//        // 这里 指定文件
//        excelWriter = EasyExcel.write(fileName).build();
//        // 去调用写入,这里我调用了五次，实际使用时根据数据库分页的总的页数来。这里最终会写到5个sheet里面
//        for (int i = 0; i < 5; i++) {
//            // 每次都要创建writeSheet 这里注意必须指定sheetNo。这里注意DemoData.class 可以每次都变，我这里为了方便 所以用的同一个class 实际上可以一直变
//            writeSheet = EasyExcel.writerSheet(i, "模板").head(DemoData.class).build();
//            // 分页去数据库查询数据 这里可以去数据库查询每一页的数据
//            List<DemoData> data = data();
//            excelWriter.write(data, writeSheet);
//        }
//        // 千万别忘记finish 会帮忙关闭流
//        excelWriter.finish();
    }

    /**
     * 图片导出
     * <p>
     * 1. 创建excel对应的实体对象 参照{@link ImageData}
     * <p>
     * 2. 直接写即可
     */
    @Test
    public void imageWrite() throws Exception {
        // 如果使用流 记得关闭
        InputStream inputStream = null;
        try {
            List<ImageData> list = new ArrayList<ImageData>();
            ImageData imageData = new ImageData();
            list.add(imageData);
            String imagePath = "E:\\temp\\test1\\file1\\测试二.jpg";
            // 放入五种类型的图片 实际使用只要选一种即可
//            1 . byte 数组
            imageData.setByteArray(FileUtils.readFileToByteArray(new File(imagePath)));
//            2. File对象
            imageData.setFile(new File(imagePath));
//            3. 文件路径
            imageData.setString(imagePath);
//            4. 输入流
            inputStream = FileUtils.openInputStream(new File(imagePath));
            imageData.setInputStream(inputStream);
//            5. 网络地址
            imageData.setUrl(new URL(
                    "https://img.zcool.cn/community/01b2945b0663dda801218cf4617993.jpg@3000w_1l_0o_100sh.jpg"));
            EasyExcel.write(fileName, ImageData.class).sheet().doWrite(list);
        } finally {
            if (inputStream != null) {
                inputStream.close();
            }
        }
    }


    /**
     * 在下一行追加。
     * 根据模板写入
     * <p>1. 创建excel对应的实体对象 参照{@link IndexData}
     * <p>3. 使用withTemplate 写取模板
     * <p>4. 直接写即可
     */
    @Test
    public void templateWrite() {
        String templateFileName ="C:\\Users\\Administrator\\Desktop\\excel\\excel1.xls";
        String fileName1 = "C:\\Users\\Administrator\\Desktop\\excel\\excel11.xls";
//        再原本的文件内追加新的文件并且保存到新的位置。
        EasyExcel.write(fileName1, DemoData.class).withTemplate(templateFileName).sheet().doWrite(data());
    }
}

